@import '../base/theme.scss';

/**
 * Override extending the default palette giving new values. It will extend
 * the default values of the palette if has a property missing.
 * ---
 * Usage example:
 *
 * @include md-override-palette ((
 *   accent: blue,
 *   theme: "dark"
 * ))
 *
 * ---
 * @access public
 * @param {map} $palette —  The new palette
 */

@mixin md-override-palette ($palette) {
  $md-default-palette: map-merge($md-default-palette, $palette) !global;
}


/**
 * Create a new theme based on a given palette. It will extend the default
 * values of the palette if has a property missing.
 * ---
 * Usage example:
 *
 * @include md-register-theme("alternative", (
 *   primary: #212121,
 *   accent: #CDDC39,
 *   theme: dark
 * ));
 *
 * ---
 * @access public
 * @param {string} $name —  The theme name to be used with the Vue Material
 * @param {map} $palette [$md-default-palette] —  The theme palette
 */

@mixin md-register-theme ($name, $palette: $md-default-palette) {
  $palette: map-merge($md-default-palette, $palette);
  $theme: map-merge($md-themes, (
    #{$name}: $palette
  ));

  :root {
    @each $type, $value in $palette {
      --md-theme-#{$name}-#{$type}: #{$value}
    }
  }

  $md-themes: $theme !global;
  $md-theme-name: $name !global;

  @include md-base-theme;
}


/**
 * Theme pieces of a given scss code for all pre registered themes.
 * ---
 * Usage example:
 *
 * .md-button {
 *   min-width: 88px;
 *   height: 40px;
 *   display: inline-block;
 *   border-radius: 2px;
 *   transition: .3s ease;
 *
 *   @include md-theme-component() {
 *     background: md-theme(primary);
 *     color: md-theme(text-primary);
 *   }
 *
 *   &.md-accent {
 *     @include md-theme-component() {
 *       background: md-theme(accent);
 *       color: md-theme(text-accent);
 *     };
 *   }
 * }
 */

@mixin md-theme-component () {
  @each $theme, $palette in $md-themes {
    $md-theme-palette: map-merge($md-theme-palette, $palette) !global;
    $md-current-theme: $theme !global;

    @if( $theme == $md-theme-name or $md-theme-name == 'all' ) {
      &.md-theme-#{$theme} {
        @content;
      }
    }
  }
}


/**
 * Theme pieces of a given scss code for all pre registered themes based on parent.
 * ---
 * Usage example:
 *
 * .md-foo {
 *   @include md-theme-component-relative() {
 *     @include md-theme-property(background, primary);
 *   }
 * }
 */

@mixin md-theme-component-relative () {
  @each $theme, $palette in $md-themes {
    $md-theme-palette: map-merge($md-theme-palette, $palette) !global;
    $md-current-theme: $theme !global;

    @if( $theme == $md-theme-name or $md-theme-name == 'all' ) {
      .md-theme-#{$theme} & {
        @content;
      }
    }
  }
}


/**
 * Theme a single css property
 * ---
 * Usage example:
 *
 * .md-button {
 *   min-width: 88px;
 *   height: 40px;
 *   display: inline-block;
 *   border-radius: 2px;
 *   transition: .3s ease;
 *
 *   @include md-theme-component() {
 *     @include md-theme-property(background, primary);
 *     @include md-theme-property(color, text-primary, primary);
 *   }
 *
 *   &.md-accent {
 *     @include md-theme-component() {
 *       @include md-theme-property(background, accent);
 *       @include md-theme-property(color, text-primary, accent);
 *     }
 *   }
 * }
 *
 * ---
 * @access public
 * @param {string} $property —  The css property
 * @param {string} $type —  A palette type
 * @param {string} $background —  The background color to analyse contrast
 * @param {number} $opacity —  The opacity amount
 */

@mixin md-theme-property ($property, $type, $background: "", $opacity: "") {
  $value: md-theme($type, $background);
  $variant: null;

  @if $background != "" {
    $variant: -on-#{$background};
  }

  @if $opacity != "" {
    $value: rgba($value, $opacity);
  }

  #{$property}: $value;
  #{$property}: var(--md-theme-#{$md-current-theme}-#{$type}#{$variant}, $value);
}

/**
 * Theme a single css property darkening the color by a certain amount
 * ---
 * Usage example:
 *
 * .md-button {
 *   min-width: 88px;
 *   height: 40px;
 *   display: inline-block;
 *   border-radius: 2px;
 *   transition: .3s ease;
 *
 *   @include md-theme-component() {
 *     @include md-theme-property-darken(background, primary, background, 10%);
 *     @include md-theme-property(color, text-primary, primary);
 *   }
 * }
 *
 * ---
 * @access public
 * @param {string} $property —  The css property
 * @param {string} $type —  A palette type
 * @param {string} $background —  The background color to analyse contrast
 * @param {string} $darken —  The darken amount to apply to the color
 */

@mixin md-theme-property-darken ($property, $type, $background: "", $darken: "") {
  $value: md-theme($type, $background);
  $variant: null;

  @if $background != "" {
    $variant: -on-#{$background};
  }

  @if $darken != "" {
    $value: darken($value, $darken);
  }

  #{$property}: $value;
  #{$property}: var(--md-theme-#{$md-current-theme}-#{$type}#{$variant}, $value);
}

/**
 * Theme a single css property by
 * ---
 * Usage example:
 *
 * .md-button {
 *   min-width: 88px;
 *   height: 40px;
 *   display: inline-block;
 *   border-radius: 2px;
 *   transition: .3s ease;
 *
 *   @include md-theme-component() {
 *     @include md-theme-property-by-hue(background, grey, 100, toolbar, background);
 *     @include md-theme-property(color, text-primary, background);
 *   }
 * }
 *
 * ---
 * @access public
 * @param {string} $property —  The css property
 * @param {string} $color —  A valid material palette color name
 * @param {string} $hue —  The hue amount to get the hex color
 * @param {string} $type —  The type of variable
 * @param {string} $variant —  The type of constrasted variable
 */

@mixin md-theme-property-by-hue ($property, $color, $hue, $type, $secondary) {
  $hex: md-get-palette-color($color, $hue);
  $variant: null;

  @if $secondary != "" {
    $variant: -#{$secondary};
  }

  #{$property}: $hex;
  #{$property}: var(--md-theme-#{$md-current-theme}-#{$type}#{variant}, $hex);
}
